/**
 * 
 */
package com.neiquan.secondhand.util;

import java.io.ByteArrayInputStream;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import org.apache.poi.POIXMLDocument;
import org.apache.poi.openxml4j.opc.OPCPackage;
import org.apache.poi.xwpf.usermodel.ParagraphAlignment;
import org.apache.poi.xwpf.usermodel.XWPFParagraph;
import org.apache.poi.xwpf.usermodel.XWPFRun;
import org.apache.poi.xwpf.usermodel.XWPFTable;
import org.apache.poi.xwpf.usermodel.XWPFTableCell;
import org.apache.poi.xwpf.usermodel.XWPFTableRow;

/** 
 * @author zhulang
 * @date 2016-5-19 下午04:53:55 
 * @descript word 工具类
 */

public class WordUtil {

	
	/** 
     * 根据指定的参数值、模板，生成 word 文档 
     * @param param 需要替换的变量 
     * @param template 模板 
     */  
    public static CustomXWPFDocument generateWord(Map<String, Object> param, String template) {  
        CustomXWPFDocument doc = null;  
        try {  
            OPCPackage pack = POIXMLDocument.openPackage(template);  
            doc = new CustomXWPFDocument(pack);  
            if (param != null && param.size() > 0) {
                  
                //处理段落  
                List<XWPFParagraph> paragraphList = doc.getParagraphs();
                //processParagraphs(paragraphList, param, doc);
            	processParagraphs(paragraphList, param, doc);
                  
                //处理表格  
                Iterator<XWPFTable> it = doc.getTablesIterator();  
                while (it.hasNext()) {  
                    XWPFTable table = it.next();  
                    List<XWPFTableRow> rows = table.getRows();  
                    for (XWPFTableRow row : rows) {
                        List<XWPFTableCell> cells = row.getTableCells();  
                        for (XWPFTableCell cell : cells) {
                            List<XWPFParagraph> paragraphListTable =  cell.getParagraphs();  
                            processParagraphs(paragraphListTable, param, doc);  
                        }
                    }
                }  
            }  
        } catch (Exception e) {  
            e.printStackTrace();  
        }  
        return doc;  
    }
    
    /**
     * 根据list字符串变量生产word文件
     * @param param
     * @return
     */
    public static CustomXWPFDocument generateWord(List<String> param) {
    	CustomXWPFDocument doc = new CustomXWPFDocument();  
        try {  
            if (param != null && param.size() > 0) {
            	XWPFParagraph parag = null;
            	XWPFRun valueRun = null;
            	for (int i = 0 ; i < param.size(); i ++) {
            		String value = param.get(i);
            		// <br>标识需要换行、重新创建段落
            		if (value.indexOf("<br>") != -1) {
        	    		String [] values = value.split("<br>");
        	    		for(int j = 0; j < values.length; j++) {
        	        	    parag = doc.createParagraph();
        	        	    valueRun = parag.createRun();
        	        	    valueRun.setText(values[j]);
        	        	    valueRun.setFontSize(13);
        	        	    valueRun.setColor("0968F7");
        	        	}
        	    	} /*else if (value.indexOf("picture") != -1){
        	    		String [] pictures = value.split(",");
        	    		// 处理图片
        	    		byte[] byteArray = WordUtil.inputStream2ByteArray(new FileInputStream(pictures[1]), true);
        	    		ByteArrayInputStream byteInputStream = new ByteArrayInputStream(byteArray);
        	    		int picType = getPictureType("jpg");
        	    		String picId = doc.addPictureData(byteInputStream,picType);
        	    		doc.createPicture(doc.getAllPictures().size() - 1, 300 , 150, doc.createParagraph());
        	    	}*/ else {
        	    		parag = doc.createParagraph();
    	        	    valueRun = parag.createRun();
    	        	    valueRun.setText(value);
    	        	    valueRun.setFontSize(13);
    	        	    valueRun.setColor("0968F7");
        	    	}
            	}
            	XWPFParagraph firstPar = doc.getParagraphs().get(0);
            	firstPar.setAlignment(ParagraphAlignment.CENTER);
            	XWPFRun firstRun = firstPar.getRuns().get(0);
            	firstRun.setBold(true);
            	firstRun.setFontSize(15);
            	firstRun.setColor("010D10");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return doc;  
    }
    
    /**
     * 根据list字符串变量生产word文件
     * @param param list<Object> 类型参数,手动加上<br>标识换行,图片值为Map类型
     * @return
     */
    public static CustomXWPFDocument generateWord2(List<Object> param) {
    	CustomXWPFDocument doc = new CustomXWPFDocument();  
        try {  
            if (param != null && param.size() > 0) {
            	XWPFParagraph parag = null;
            	XWPFRun valueRun = null;
            	String value = "";
            	for (int i = 0 ; i < param.size(); i ++) {
            		Object obj = param.get(i);
            		if (obj instanceof String) {
            			value = obj.toString();
            			// <br>标识需要换行、重新创建段落
                		if (value.indexOf("<br>") != -1) {
            	    		String [] values = value.split("<br>");
            	    		for(int j = 0; j < values.length; j++) {
            	        	    parag = doc.createParagraph();
            	        	    valueRun = parag.createRun();
            	        	    valueRun.setText(values[j]);
            	        	    valueRun.setFontSize(13);
            	        	    valueRun.setColor("0968F7");
            	        	}
            	    	} else {
            	    		parag = doc.createParagraph();
        	        	    valueRun = parag.createRun();
        	        	    valueRun.setText(value);
        	        	    valueRun.setFontSize(13);
        	        	    valueRun.setColor("0968F7");
            	    	}
            		} else if (obj instanceof Map) {
            			Map pic = (Map)obj;
                        int width = Integer.parseInt(pic.get("width").toString());
                        int height = Integer.parseInt(pic.get("height").toString());
                        int picType = getPictureType(pic.get("type").toString());
                        int count = Integer.parseInt(pic.get("count").toString());
                        // 图片数量为1 content保存的是对象流,多图片保存的为多路径或者图片ID字符串,根据业务情况来定,这里根据路径来处理
                        if (count == 1) {
                        	byte[] byteArray = (byte[]) pic.get("content");
                            ByteArrayInputStream byteInputStream = new ByteArrayInputStream(byteArray);
                        	String picId = doc.addPictureData(byteInputStream,picType);
                            doc.createPicture(doc.getAllPictures().size() - 1, width , height, doc.createParagraph());
                        } else {
                        	String content = pic.get("content").toString();
                        	if (content != null && !"".equals(content)) {
                        		String [] paths = content.split(",") ;
                        		for (String path : paths) {
                        			byte[] byteArray = WordUtil.inputStream2ByteArray(new FileInputStream(path), true);
                    	    		ByteArrayInputStream byteInputStream = new ByteArrayInputStream(byteArray);
                    	    		String picId = doc.addPictureData(byteInputStream,picType);
                    	    		doc.createPicture(doc.getAllPictures().size() - 1, 300 , 150, doc.createParagraph());
                        		}
                        	}
                        }
            		}
            	}
            	XWPFParagraph firstPar = doc.getParagraphs().get(0);
            	firstPar.setAlignment(ParagraphAlignment.CENTER);  
            	XWPFRun firstRun = firstPar.getRuns().get(0);
            	firstRun.setBold(true);
            	firstRun.setFontSize(15);
            	firstRun.setColor("010D10");
            }
        } catch (Exception e) {
            e.printStackTrace();  
        }
        return doc;
    }
    
    /**
     * 处理段落 
     * @param paragraphList
     * @param param Map格式的参数,图片格式值为Map
     * @param doc 模板文档对象
     */
    public static void processParagraphs(List<XWPFParagraph> paragraphList,Map<String, Object> param,CustomXWPFDocument doc){
        if(paragraphList != null && paragraphList.size() > 0){
            for(int i = 0; i < paragraphList.size(); i ++) {
            	XWPFParagraph paragraph = paragraphList.get(i);
                List<XWPFRun> runs = paragraph.getRuns();
                for (XWPFRun run : runs) {
                    String text = run.getText(0);  
                    if(text != null){
                        boolean isSetText = false;
                        for (Entry<String, Object> entry : param.entrySet()) {
                            String key = entry.getKey();
                            if(text.indexOf(key) != -1){
                                isSetText = true;
                                Object value = entry.getValue();
                                if (value instanceof String) {
                                	//文本替换
                                    text = text.replace(key, value.toString());
                                } else if (value instanceof Map) {
                                	//图片替换
                                    text = text.replace(key, "");
                                    Map pic = (Map)value;
                                    int width = Integer.parseInt(pic.get("width").toString());
                                    int height = Integer.parseInt(pic.get("height").toString());
                                    int picType = getPictureType(pic.get("type").toString());
                                    byte[] byteArray = (byte[]) pic.get("content");
                                    ByteArrayInputStream byteInputStream = new ByteArrayInputStream(byteArray);
                                    try {
                                    	String type = doc.addPictureData(byteInputStream,picType);
                                        doc.createPicture(doc.getAllPictures().size() - 1, width , height,paragraph);
                                    } catch (Exception e) {
                                        e.printStackTrace();
                                    }
                                }
                            }
                        }
                        if(isSetText){
                        	run.setText(text,0);
                        }
                    }
                }
            }
        }
    }
    
    /** 
     * 根据图片类型，取得对应的图片类型代码 
     * @param picType 
     * @return int 
     */  
    private static int getPictureType(String picType){
        int res = CustomXWPFDocument.PICTURE_TYPE_PICT;  
        if(picType != null){  
            if(picType.equalsIgnoreCase("png")){  
                res = CustomXWPFDocument.PICTURE_TYPE_PNG;  
            }else if(picType.equalsIgnoreCase("dib")){  
                res = CustomXWPFDocument.PICTURE_TYPE_DIB;  
            }else if(picType.equalsIgnoreCase("emf")){  
                res = CustomXWPFDocument.PICTURE_TYPE_EMF;  
            }else if(picType.equalsIgnoreCase("jpg") || picType.equalsIgnoreCase("jpeg")){  
                res = CustomXWPFDocument.PICTURE_TYPE_JPEG;  
            }else if(picType.equalsIgnoreCase("wmf")){  
                res = CustomXWPFDocument.PICTURE_TYPE_WMF;  
            }  
        }
        return res;  
    }
    
    /** 
     * 将输入流中的数据写入字节数组 
     * @param in 
     * @return 
     */  
    public static byte[] inputStream2ByteArray(InputStream in,boolean isClose){  
        byte[] byteArray = null;  
        try {  
            int total = in.available();  
            byteArray = new byte[total];  
            in.read(byteArray);  
        } catch (IOException e) {  
            e.printStackTrace();  
        }finally{  
            if(isClose){  
                try {  
                    in.close();  
                } catch (Exception e2) {  
                    System.out.println("关闭流失败");  
                }  
            }  
        }  
        return byteArray;  
    }
	
}

